import { API } from '@/services/common/api'
import {
  ContactType,
  splitContactId,
  isWechatWxid,
  isQywxWxid,
  formatRawBaseContact,
  type RawContactMeta,
  type RawBaseContact,
} from '@/services/contacts'
import type { MuteGroup, GroupExtra, GroupTag, GroupContact } from './definition'

/**
 * 获取群列表
 * tags: 若指定了此属性，则为通过`群标签`搜索群
 */
type RawBase = Pick<RawBaseContact, 'conversation_id'> & RawContactMeta
interface RawGroupContact extends RawBase {
  create_time: number
  create_user_id: string
  is_external: 0 | 1
  is_creator: 0 | 1
  is_admin: 0 | 1 // 是否管理员，不过不准，忽略它
  // leader_id: string | null // 作用未知
  nickname: string
  total: number
  wx_id: string
  Remark: string | null
}
export function formatRawGroupContact(raw: RawGroupContact): GroupContact {
  const compatible = {
    ...raw,
    user_id: raw.conversation_id, // 群的 userId 就是其 conversationId
    avatar: '', // 目前企业微信群没有头像
    remark: raw.Remark ?? '', // 群备注数据是后端提供的，不是 hook 自带的
    username: raw.nickname, // 群数据里没有返回 username，而是返回了 nickname
    realname: '',
  }
  return {
    type: ContactType.group,
    created: raw.create_time,
    creatorWxid: raw.create_user_id,
    isExternal: !!raw.is_external,
    isOwner: !!raw.is_creator,
    total: raw.total,
    ...formatRawBaseContact(raw.wx_id, compatible),
  }
}
export async function getGroups(wxids: string[], tags: number[] = []) {
  return API('/Room/RoomList', {
    data: {
      wxids,
      labelIds: tags,
    },
    formatter: (raw: RawGroupContact[]) => raw.map(formatRawGroupContact),
  })
}

/**
 * ===============================
 * 群成员
 * ===============================
 */

/**
 * 加载群成员列表
 */
interface RawGroupMember extends Omit<RawBaseContact, 'conversation_id'> {
  invite_user_id: string
  is_admin: 0 | 1
  room_nickname: string
  join_scene: number
  join_time: number // 时间戳（秒）
}
export async function loadGroupMembers(contactId: string) {
  const [ownerWxid, conversationId] = splitContactId(contactId)
  return API('/Room/RoomMemberList', {
    data: { wxid: ownerWxid, conversationId },
    formatter(raw: RawGroupMember[]) {
      return raw
        .map(item =>
          formatRawBaseContact(ownerWxid, {
            ...item,
            username: item.room_nickname || item.username, // 有群昵称（群成员在群里给自己设置的昵称）的情况下，优先显示群昵称
            conversation_id: conversationId,
          }),
        )
        .filter(v => isWechatWxid(v.userId) || isQywxWxid(v.userId))
    },
  })
}

/**
 * 拉群
 * wxid: 群主的 wxid
 * members: 群成员的 wxid，不需要包含群主
 */
export interface RawCreatedGroup {
  createruin: string // 群主 wxid
  createtime: number // 创建时间（时间戳，秒）
  roomid: string // 群 wxid（用于拼装成群的 conversation id）
  roomname: '' // 群名称目前收到的都是空字符串
  success_add_vidlist: { success_add_vidlist: string }[] // 初始群成员列表，success_add_vidlist 是成员的 wxid

  msgid: number
  msgseq: number
  sessionid: string
  error_code: 0
  error_message: ''
  failmem: [{ type: 0; vid: 0 }]
}
export function formatRawCreatedGroup(ownerWxid: string, raw: RawCreatedGroup): GroupContact {
  const rawGroup = {
    conversation_id: `R:${raw.roomid}`,
    create_time: Date.now(),
    create_user_id: raw.createruin,
    is_creator: 1,
    is_external: 1, // 注意！此方法生成的群联系人，无法获知其是否是“外部群”。仅应作为临时填充使用，然后立即重新加载群列表。
    is_admin: 1,
    nickname: raw.roomname,
    total: raw.success_add_vidlist.length,
    wx_id: ownerWxid,
    Remark: null,
    LastChatTimestamp: 0,
  } as const
  return formatRawGroupContact(rawGroup)
}
export async function createGroup(ownerWxid: string, members: string[]) {
  return API('/Room/CreateRoom', {
    data: { wxid: ownerWxid, memberWxIds: members.join(',') },
    formatter: formatRawCreatedGroup.bind(null, ownerWxid),
  })
}

/**
 * 拉群完成的推送
 */
export interface HookCreatedGroup {
  member_list: { name: string; user_id: string }[]
  op_user_id: string
  op_user_name: string
  room_conversation_id: string
  room_name: string
}
export function formatHookCreatedGroup(ownerWxid: string, raw: HookCreatedGroup) {
  const rawGroup = {
    conversation_id: raw.room_conversation_id,
    create_time: Date.now(),
    create_user_id: raw.op_user_id,
    is_creator: 1,
    is_external: 1, // 注意！此方法生成的群联系人，无法获知其是否是“外部群”。仅应作为临时填充使用，然后立即重新加载群列表。
    is_admin: 1,
    nickname: raw.room_name,
    total: raw.member_list.length,
    wx_id: ownerWxid,
    Remark: null,
    LastChatTimestamp: 0,
  } as const
  return formatRawGroupContact(rawGroup)
}

/**
 * 批量添加群成员
 */
export async function addGroupMember(contactId: string, members: string[]) {
  const [ownerWxid, conversationId] = splitContactId(contactId)
  return API('/Room/AddRoomMember', {
    data: {
      wxid: ownerWxid,
      conversationId,
      memberWxIds: members.join(','),
    },
    formatter() {},
  })
}

/**
 * 批量删除群成员
 */
export async function removeGroupMember(contactId: string, members: string[]) {
  const [ownerWxid, conversationId] = splitContactId(contactId)
  return API('/Room/DeleteRoomMembers', {
    data: {
      wxid: ownerWxid,
      conversationId,
      memberWxIds: members.join(','),
    },
    formatter() {},
  })
}

/**
 * 群成员加好友
 */
export async function applyGroupMember(contactId: string, memberUserId: string, verify: string) {
  const [ownerWxid, conversationId] = splitContactId(contactId)
  return API('/Room/AddRoomUser', {
    data: {
      wxid: ownerWxid,
      conversationId,
      memberWxid: memberUserId,
      verify,
    },
    formatter() {},
  })
}

/**
 * 批量发送群公告
 * （只有群主或管理员能设置成功）
 */
export async function updateGroupNotice(
  content: string,
  groups: { ownerWxid: string; conversationId: string }[],
) {
  return API('/Room/SendRoomNotice', {
    data: {
      rooms: groups.map(({ ownerWxid, conversationId }) => ({ wxid: ownerWxid, conversationId })),
      content,
    },
  })
}

/**
 * ===============================
 * 群静音
 * ===============================
 */

/**
 * 返回静音了的群的列表
 */
export async function getMuteGroups() {
  return API('/NotDisturb/GetNotDisturbs', {
    formatter(raw: { WxId: string; ConversationId: string; Id: number }[]): MuteGroup[] {
      return raw.map(v => ({ id: v.Id, conversationId: v.ConversationId, wxid: v.WxId }))
    },
  })
}

/**
 * 将指定群标记为静音
 */
export async function muteGroup(contactId: string) {
  const [ownerWxid, conversationId] = splitContactId(contactId)
  return API('/NotDisturb/AddNotDisturb', { data: { wxid: ownerWxid, conversationId } })
}

/**
 * 取消标记为静音
 */
export async function cancelMuteGroup(muteId: number) {
  return API('/NotDisturb/RemoveNotDisturb', { data: { id: muteId } })
}

/**
 * ===============================
 * 群资料
 * ===============================
 */

/**
 * 获取群额外资料
 */
interface RawGroupExtra {
  Remark: string
  Desc: string
}
function formatRawGroupExtra(raw: RawGroupExtra): GroupExtra {
  return {
    describe: raw.Desc,
  }
}
export async function getGroupExtra(contactId: string) {
  const [ownerWxid, conversationId] = splitContactId(contactId)
  return API('/Room/GetRoomExtendInfo', {
    data: {
      wxid: ownerWxid,
      conversationId,
    },
    formatter(raw: RawGroupExtra | null) {
      return raw ? formatRawGroupExtra(raw) : { describe: '' }
    },
  })
}

/**
 * 修改群资料
 */
interface UpdateInfo {
  remark: GroupContact['remark']
  describe: GroupExtra['describe']
}
export async function updateGroupExtra(contactId: string, info: UpdateInfo) {
  const [ownerWxid, conversationId] = splitContactId(contactId)
  return API('/Room/SaveRoomExtendInfo', {
    data: {
      wxid: ownerWxid,
      conversationId,
      remark: info.remark,
      desc: info.describe,
    },
  })
}

/**
 * ===============================
 * 群标签
 * ===============================
 */

interface RawGroupTag {
  Id: number
  Name: string
}
function formatRawGroupTag(raw: RawGroupTag) {
  return { id: raw.Id, name: raw.Name }
}

/**
 * 拉取所有可用的群标签
 */
export async function getGroupTags() {
  return API('/Room/GetRoomLabels', {
    formatter(raw: RawGroupTag[]) {
      return raw.map(formatRawGroupTag)
    },
  })
}

/**
 * 创建群标签
 */
export async function addGroupTag(name: string) {
  return API('/Room/AddRoomLabel', {
    data: { name },
    formatter(id: number): GroupTag {
      return { id, name }
    },
  })
}

/**
 * 删除群标签
 */
export async function removeGroupTag(id: number) {
  return API('/Room/RemoveRoomLabel', {
    data: { id },
  })
}

/**
 * 获取指定群绑定了的群标签
 */
export async function getBoundGroupTags(contactId: string) {
  const [ownerWxid, conversationId] = splitContactId(contactId)
  return API('/Room/GetRoomLabelRelations', {
    data: { wxid: ownerWxid, conversationId },
    formatter(raw: RawGroupTag[]) {
      return raw.map(formatRawGroupTag)
    },
  })
}

/**
 * 绑定群标签
 */
export async function bindGroupTag(contactId: string, tagId: number) {
  const [ownerWxid, conversationId] = splitContactId(contactId)
  return API('/Room/AddRoomLabelRelation', {
    data: { wxid: ownerWxid, conversationId, labelId: tagId },
  })
}

/**
 * 解绑群标签
 */
export async function unbindGroupTag(contactId: string, tagId: number) {
  const [ownerWxid, conversationId] = splitContactId(contactId)
  return API('/Room/RemoveRoomLabelRelation', {
    data: { wxid: ownerWxid, conversationId, labelId: tagId },
  })
}
